package com.zz.common.exception;

import com.zz.common.base.dto.ResponseDTO;
import com.zz.common.base.enums.BaseExceptionEnum;
import org.springframework.core.annotation.Order;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.validation.BindingResult;
import org.springframework.validation.FieldError;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestControllerAdvice;

import java.net.ConnectException;
import java.util.ArrayList;
import java.util.List;

/**
 * @author zl
 * @version 1.0
 * <p>
 * 全局异常处理
 */
@Order(1)
@RestControllerAdvice
public class ExceptionGlobalHandler {

    /**
     * 处理数据校验异常
     */
    @ExceptionHandler(MethodArgumentNotValidException.class)
    @ResponseBody
    public ResponseDTO<String> handleMethodArgumentNotValidException(MethodArgumentNotValidException ex) {
        BindingResult bindingResult = ex.getBindingResult();
        StringBuilder sb = new StringBuilder("数据校验失败：");
        List<String> arr = new ArrayList<>();
        FieldError lastFieldError = null;
        for (FieldError fieldError : bindingResult.getFieldErrors()) {
            if (!arr.contains(fieldError.getDefaultMessage())) {
                sb.append(fieldError.getDefaultMessage()).append(", ");
                arr.add(fieldError.getDefaultMessage());
            }
            lastFieldError = fieldError;
        }
        if (lastFieldError != null) {
            sb.deleteCharAt(sb.lastIndexOf(","));
        }
        String msg = sb.toString();
        return new ResponseDTO(BaseExceptionEnum.VALIDATION_ERROR.getCode(), msg, "");
    }

    /**
     * 处理业务异常
     */
    @ExceptionHandler(BaseException.class)
    @ResponseBody
    public ResponseDTO<String> handleBaseException(BaseException ex) {
        String msg = "业务异常：" + ex.getMessage();
        return new ResponseDTO(ex.getCode(), msg, "");
    }

    /**
     * 处理连接异常
     */
    @ExceptionHandler(ConnectException.class)
    @ResponseBody
    public ResponseDTO<String> handleConnectException(ConnectException ex) {
        String msg = "连接异常：" + ex.getMessage();
        return new ResponseDTO(BaseExceptionEnum.INTERNAL_SERVER_ERROR.getCode(), msg, "");
    }

    /**
     * 处理JSON解析异常
     *
     * @param ex
     * @return
     */
    @ExceptionHandler(HttpMessageNotReadableException.class)
    public ResponseDTO<String> handleJsonParseError(HttpMessageNotReadableException ex) {
        String msg = "JSON解析异常：" + ex.getMessage();
        return new ResponseDTO(BaseExceptionEnum.VALIDATION_ERROR.getCode(), msg, "");
    }
}
